home *** CD-ROM | disk | FTP | other *** search
/ Programming Languages Suite / ProgLangD.iso / BORLAND TURBO / STDLIB.PAK / CONCORD.CPP < prev    next >
C/C++ Source or Header  |  1997-05-06  |  3KB  |  116 lines

  1. /**************************************************************************
  2.  *
  3.  * concord.cpp - Concordance sample program. Section 9.3.3
  4.  *
  5.  * $Id: concord.cpp,v 1.5 1995/08/29 19:01:16 oberg Exp $
  6.  *
  7.  * $$RW_INSERT_HEADER "slyrs.cpp"
  8.  *
  9.  **************************************************************************/
  10.  
  11. # include <map>
  12. # include <list>
  13. # include <iostream.h>
  14. # include <string>
  15. using namespace std;
  16.  
  17.     // define < for strings
  18. bool operator < (const string & left, const string & right)
  19. {    return left.compare(right) < 0; }
  20.  
  21.  
  22.     // split a line of text into words
  23. void split
  24.     (const string & text, const string & separators, list<string> & words)
  25. {
  26.     int n = text.length();
  27.     int start, stop;
  28.     
  29.     start = text.find_first_not_of(separators);
  30.     while ((start >= 0) && (start < n)) {
  31.         stop = text.find_first_of(separators, start);
  32.         if ((stop < 0) || (stop > n)) stop = n;
  33.         words.push_back (text.substr(start, stop-start));
  34.         start = text.find_first_not_of(separators, stop+1);
  35.         }
  36.         
  37. }
  38.  
  39.  
  40. class concordance {
  41.     typedef multimap<string, int, less<string> > wordDictType;
  42. public:
  43.  
  44.     void addWord (string, int);
  45.     void readText (istream &);
  46.     void printConcordance (ostream &);
  47.     
  48. private:
  49.     wordDictType wordMap;
  50. };
  51.  
  52. void concordance::addWord (string word, int line)
  53. {
  54.         // see if word occurs in list
  55.         // first get range of entries with same key
  56.     wordDictType::iterator low = wordMap.lower_bound(word);
  57.     wordDictType::iterator high = wordMap.upper_bound(word);
  58.         // loop over entires, see if any match current line
  59.     for ( ; low != high; ++low)
  60.         if ((*low).second == line)
  61.             return;
  62.         // didn't occur, add now
  63.     wordMap.insert(wordDictType::value_type(word, line));
  64. }
  65.  
  66. # include <ctype.h>
  67. void allLower (string & s)
  68. {
  69.     for (int i = 0; i < s.size(); i++)
  70.         if (isupper(s[i]))
  71.             s[i] = tolower(s[i]);
  72. }
  73.  
  74. void concordance::readText (istream & in)
  75. {
  76.     string line;
  77.     for (int i = 1; getline(in, line, '\n'); i++) {
  78.         allLower(line);
  79.         list<string> words;
  80.         split(line, " ,.;:", words);
  81.         list<string>::iterator wptr;
  82.         for (wptr = words.begin(); wptr != words.end(); ++wptr)
  83.             addWord(*wptr, i);
  84.         }
  85. }
  86.  
  87. void concordance::printConcordance (ostream & out)
  88. {
  89.     string lastword("");
  90.     wordDictType::iterator pairPtr;
  91.     wordDictType::iterator stop = wordMap.end();
  92.     for (pairPtr = wordMap.begin(); pairPtr != stop; ++pairPtr)
  93.             // if word is same as previous, just print line number
  94.         if (lastword == (*pairPtr).first)
  95.             out << " " << (*pairPtr).second;
  96.         else {    // first entry of word
  97.             lastword = (*pairPtr).first;
  98.             cout << endl << lastword << ": " << (*pairPtr).second;
  99.             }
  100.     cout << endl; // terminate last line
  101. }
  102.  
  103. int main() {
  104.     cout << "Concordance sample program, from Chapter 7" << endl;
  105.     cout << "Enter text, then end-of-file:" << endl;
  106.     concordance words;
  107.         
  108.     words.readText(cin);    
  109.     
  110.     words.printConcordance(cout);
  111.  
  112.     cout << "End of concordance sample program" << endl;
  113.  
  114.     return 0;
  115. }
  116.